<?php
namespace app\api\controller;
use app\model\VipIcon as VipIconModel;
use app\model\Token as TokenModel;
use think\Db;

use app\lib\baidu\Api as baiduApi;


class Sse extends Base
{   
    protected $noCheckToken = ['callBaiduWorkshopSSE','main'];
    
    
    public function callBaiduWorkshopSSE($url, $access_token, $body, $onMessage)
    {
        return (new class() {
            private $buffer = "";
            private $dataMsgBuffer = "";

            public function call($url, $access_token, $body, $onMessage)
            {
                $body['stream'] = true;
                $curl = curl_init();
                curl_setopt_array($curl, array(
                    CURLOPT_URL => $url . '?access_token=' . $access_token,
                    CURLOPT_RETURNTRANSFER => true,
                    CURLOPT_ENCODING => '',
                    CURLOPT_MAXREDIRS => 10,
                    CURLOPT_TIMEOUT => 0,
                    CURLOPT_FOLLOWLOCATION => true,
                    CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
                    CURLOPT_CUSTOMREQUEST => 'POST',
                    CURLOPT_POSTFIELDS => json_encode($body),
                    CURLOPT_HTTPHEADER => array(
                        'Content-Type: application/json'
                    ),
                    CURLOPT_WRITEFUNCTION => function ($curl, $str) use ($onMessage) {
                        $this->buffer = $this->buffer . $str;
                        $lines = explode("\n", $this->buffer);
                        $this->buffer = array_pop($lines);
                        foreach ($lines as $line) {
                            if ($line == "") { //读取到空行，一个数据块发送完成
                                $onMessage([
                                    "type" => "DATA",
                                    "content" => json_decode($this->dataMsgBuffer)
                                ]);
                                $this->dataMsgBuffer = "";
                                continue;
                            }
                            $msgPart = explode(":", $line, 2);
                            $type = $msgPart[0];
                            $content = $msgPart[1];
                            if ($type == 'data') { //数据块没有收到空行之前放入buffer中
                                $this->dataMsgBuffer = $this->dataMsgBuffer . trim($content);
                            } else if ($type == '' && $content != '') { //服务端发送的注释，用于保证链接不断开
                                $onMessage([
                                    "type" => "COMMENT",
                                    "content" => trim($content)
                                ]);
                            } else {
                                $onMessage([
                                    "type" => $type,
                                    "content" => trim($content)
                                ]);
                            }
                        }
                        return strlen($str);
                    }
                ));
                curl_exec($curl);
                if (curl_errno($curl)) {
                    $onMessage([
                        "type" => "ERROR",
                        "content" => curl_strerror(curl_errno($curl))
                    ]);
                } else {
                    $onMessage([
                        "type" => "END"
                    ]);
                }
                curl_close($curl);
            }
        })->call($url, $access_token, $body, $onMessage);
    }

    public function main(){
        $api = new baiduApi();
        $api_param = '{"client_id":"YeyMF21dXex0vmVjUP5Z044G","client_secret":"IoFoQbHWLmf0c8t9VGXM9baYqIOqfbD7"}';
        $api_param = json_decode($api_param,true);
        $token = $api->token($api_param);
        if (empty($token['access_token'])) {
            return json(['code'=>5000,'msg'=>'token获取失败']);
        }

        $url = 'https://aip.baidubce.com/rpc/2.0/ai_custom/v1/wenxinworkshop/chat/completions_pro';
        $access_token = $token['access_token'];
        $body = [
            "messages" => [
                ["role" => "user", "content" => "给我推荐一些自驾游路线"]
            ]
        ];

        $this->callBaiduWorkshopSSE($url, $access_token, $body, function ($msg) {
            if ($msg["type"] == "DATA") {
                echo($msg["content"]->result);
            } else if ($msg["type"] == "END") {
                echo("\n响应返回结束\n");
            } else {
                var_dump($msg);
            }
        });
    }

   


}
